home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
MacUser ROM 45
/
MACUSER-ROM-VOL-45-1997-08.ISO.7z
/
MACUSER-ROM-VOL-45-1997-08.ISO
/
本誌連動
/
第9回:ウイークエンドデベロッパーへの道
/
QuickCinema 1.0
/
Source code
/
MovieTheater.c
< prev
next >
Wrap
Text File
|
1997-04-28
|
14KB
|
428 lines
/*------------------------------------------------------------------------------
* プログラム名: QuickCinema 1.0.0
* ファイル名: MovieTheater.c
*-----------------------------------------------------------------------------*/
#include "QuickCinema.h"
#include "ProtoType.h"
//----------------------------------------------------------------------------------//
// 定数定義 //
//----------------------------------------------------------------------------------//
//----------------------------------------------------------------------------------//
// グローバル変数 //
//----------------------------------------------------------------------------------//
extern Boolean gQuitApplication;
extern Boolean gIsBackground;
extern SInt32 gSleepTime;
extern AEAddressDesc gSelfAddress;
//----------------------------------------------------------------------------------//
// プロトタイプ //
//----------------------------------------------------------------------------------//
static OSErr LoadMovieFile(MovieInfoHandle movieInfoHdl, Movie *theMovie);
static Boolean ShowMovieWindow(Movie theMovie, MovieInfoHandle movieInfoHdl);
static Boolean IsOpenedMovieFIle(const FSSpec *fileSpec);
//----------------------------------------------------------------------------------//
// ムービーに対するイベント処理 //
//----------------------------------------------------------------------------------//
Boolean HandleMovieTask(const EventRecord *event)
{
WindowRef window;
MovieInfoHandle movieInfoHdl;
MovieController controller;
Boolean catchedEvent = false;
window = FrontWindow();
while (window != nil)
{
// ムービーウィンドウであるか確認する
if (IsMovieWindow(window))
{
movieInfoHdl = (MovieInfoHandle)GetWRefCon(window);
if (movieInfoHdl)
{
controller = (*movieInfoHdl)->controller;
// ムービーに対するイベント処理をコントローラに委ねる
if (MCIsPlayerEvent(controller, event))
catchedEvent = true;
}
}
window = (WindowPtr)(((WindowPeek)window)->nextWindow);
}
// コントローラがイベントを処理した場合:true
// コントローラがイベントを処理しなかった場合:false
return catchedEvent;
}
//----------------------------------------------------------------------------------//
// ムービー専用編集メニュー処理 //
//----------------------------------------------------------------------------------//
void HandleMovieEditMenu(WindowRef window, short menuItem)
{
MovieInfoHandle movieInfoHdl;
MovieController controller;
Movie aMovie = nil;
ComponentResult compErr;
movieInfoHdl = (MovieInfoHandle)GetWRefCon(window);
controller = (*movieInfoHdl)->controller;
switch (menuItem)
{
// Undoメニュー項目を処理する
case iUndo:
compErr = MCUndo(controller);
break;
// Cutメニュー項目を処理する 選択したムービーが返される
case iCut:
aMovie = MCCut(controller);
break;
// Copyメニュー項目を処理する 選択したムービーが返される
case iCopy:
aMovie = MCCopy(controller);
break;
// Pasteメニュー項目を処理する
case iPaste:
compErr = MCPaste(controller, nil);
break;
// Clearメニュー項目を処理する
case iClear:
compErr = MCClear(controller);
break;
}
if (aMovie)
{
// 取得したムービーをスクラップに保存する
PutMovieOnScrap(aMovie, 0);
DisposeMovie(aMovie);
}
}
//----------------------------------------------------------------------------------//
// ムービーファイル選択処理 //
//----------------------------------------------------------------------------------//
Boolean HandleOpenMovie(void)
{
StandardFileReply reply;
OSType fileType = MovieFileType;
Movie movieFilm = nil;
MovieInfoHandle movieInfoHdl = nil;
GrafPtr savedPort;
GetPort(&savedPort);
SetCursor(&qd.arrow);
// プレビュー付ファイル選択ダイアログを表示する
StandardGetFilePreview(nil, 1, &fileType, &reply);
SetPort(savedPort);
// キャンセルされた場合は処理を中断する
if (reply.sfGood == false)
return false;
// 選択したムービーが既に開かれているかチェックする
if (IsOpenedMovieFIle(&reply.sfFile))
return true;
movieInfoHdl = (MovieInfoHandle)NewHandleClear(sizeof(MovieInfoRec));
if ((MemError() != noErr) || (movieInfoHdl == nil))
return false;
// ムービー情報を初期化する
(*movieInfoHdl)->controller = nil;
(*movieInfoHdl)->windowType = MovieFileType;
BlockMove(&reply.sfFile, &(*movieInfoHdl)->movieFileSpec, sizeof(FSSpec));
// ファイルからムービーを読み込む
if (LoadMovieFile(movieInfoHdl, &movieFilm) != noErr)
{
DisposeHandle((Handle) movieInfoHdl);
AlertUser(eCantCreateTheater);
return false;
}
// ムービーウィンドウとコントローラを生成する
if (ShowMovieWindow(movieFilm, movieInfoHdl) == false)
{
if ((*movieInfoHdl)->controller)
DisposeMovieController((*movieInfoHdl)->controller);
if (movieFilm)
DisposeMovie(movieFilm);
DisposeHandle((Handle) movieInfoHdl);
AlertUser(eCantCreateTheater);
return false;
}
return true;
}
//----------------------------------------------------------------------------------//
// ムービーファイルの読込処理 //
//----------------------------------------------------------------------------------//
Boolean HandleReadMovieFile(FSSpec *fileSpec)
{
FInfo fndrInfo;
Movie movieFilm = nil;
MovieInfoHandle movieInfoHdl = nil;
if (FSpGetFInfo(fileSpec, &fndrInfo) != noErr)
return false;
// ムービーファイルであるかチェックする
if (fndrInfo.fdType != MovieFileType)
return false;
// 該当ムービーが既に開かれているかチェックする
if (IsOpenedMovieFIle(fileSpec))
return true;
movieInfoHdl = (MovieInfoHandle)NewHandleClear(sizeof(MovieInfoRec));
if ((MemError() != noErr) || (movieInfoHdl == nil))
return false;
// ムービー情報を初期化する
(*movieInfoHdl)->controller = nil;
(*movieInfoHdl)->windowType = MovieFileType;
BlockMove(fileSpec, &(*movieInfoHdl)->movieFileSpec, sizeof(FSSpec));
// ファイルからムービーを読み込む
if (LoadMovieFile(movieInfoHdl, &movieFilm) != noErr)
{
DisposeHandle((Handle) movieInfoHdl);
AlertUser(eCantCreateTheater);
return false;
}
// ムービーウィンドウとコントローラを生成する
if (ShowMovieWindow(movieFilm, movieInfoHdl) == false)
{
if ((*movieInfoHdl)->controller)
DisposeMovieController((*movieInfoHdl)->controller);
if (movieFilm)
DisposeMovie(movieFilm);
DisposeHandle((Handle) movieInfoHdl);
AlertUser(eCantCreateTheater);
return false;
}
return true;
}
//----------------------------------------------------------------------------------//
// ムービーデータの取得処理 //
//----------------------------------------------------------------------------------//
static OSErr LoadMovieFile(MovieInfoHandle movieInfoHdl, Movie *theMovie)
{
SInt16 movieRef, resID = 0;
OSErr err;
*theMovie = nil;
// ムービーファイルを開く
err = OpenMovieFile(&(*movieInfoHdl)->movieFileSpec, &movieRef, fsRdPerm);
if (err != noErr)
return err;
// ファイルからムービーを読み込む
err = NewMovieFromFile(theMovie, movieRef, &resID, nil, newMovieActive, nil);
// ムービーファイルを閉じる
(void) CloseMovieFile(movieRef);
return err;
}
//----------------------------------------------------------------------------------//
// ムービー再生用ウィンドウ生成 //
//----------------------------------------------------------------------------------//
static Boolean ShowMovieWindow(Movie theMovie, MovieInfoHandle movieInfoHdl)
{
WindowRef window;
Rect bounds;
MovieController controller = nil;
ComponentResult compErr;
window = GetNewCWindow(rMovieWindow, nil, (WindowRef)-1L);
if (window != nil)
{
// ムービー情報をウィンドウのRefconに格納する
SetWRefCon(window, (SInt32)movieInfoHdl);
// ムービーを表示するグラフィック環境を準備する
SetMovieGWorld(theMovie, (CGrafPtr)window, nil);
// ムービーの境界矩形を取得する
GetMovieBox(theMovie, &bounds);
// 上記矩形を座標 (0,0)にフィックスする
OffsetRect(&bounds, -bounds.left, -bounds.top);
// ムービーの境界矩形を再設定する
SetMovieBox(theMovie, &bounds);
// ムービーサイズにフィットしたコントローラを生成する
controller = NewMovieController(theMovie, &bounds, mcTopLeftMovie);
if (controller != nil)
{
// コントローラの境界矩形を取得する
compErr = MCGetControllerBoundsRect(controller, &bounds);
if (compErr == noErr)
{
(*movieInfoHdl)->controller = controller;
// コントローラのキー入力を可能にする
compErr = MCDoAction(controller, mcActionSetKeysEnabled,
(void *)true);
// コントローラにグローボックスを表示する
compErr = MCDoAction(controller, mcActionSetGrowBoxBounds,
&qd.screenBits.bounds);
// グローボックス処理のためにイベントフィルタを準備する
compErr = MCSetActionFilterWithRefCon(controller,
NewMCActionFilterWithRefConProc(ControllerFilter),
(long) window);
// コントローラの編集機能を有効にする
MCEnableEditing(controller, true);
// コントローラの幅にウィンドウを合わせる
SizeWindow(window, bounds.right, bounds.bottom, false);
// 最適なウィンドウ画面サイズに調整する
AlignWindow(window, false, nil, nil);
// ウィンドウタイトルを設定する
if ((*movieInfoHdl)->movieFileSpec.name[0] > 0)
SetWTitle(window, (*movieInfoHdl)->movieFileSpec.name);
// ウィンドウを表示する
ShowWindow(window);
} return true;
}
CloseTheWindow(window);
}
return false;
}
//----------------------------------------------------------------------------------//
// ムービー情報の破棄 //
//----------------------------------------------------------------------------------//
void DisposeMovieWindow(WindowRef window)
{
MovieInfoHandle movieInfoHdl;
Movie movieFilm;
movieInfoHdl = (MovieInfoHandle)GetWRefCon(window);
if (movieInfoHdl != nil)
{
// コントローラからムービーを取得する
movieFilm = MCGetMovie((*movieInfoHdl)->controller);
// コントローラを破棄する
if ((*movieInfoHdl)->controller)
DisposeMovieController((*movieInfoHdl)->controller);
// ムービーを破棄する
if (movieFilm)
DisposeMovie(movieFilm);
// ムービー情報を破棄する
DisposeHandle((Handle) movieInfoHdl);
// ムービーウィンドウを破棄する
DisposeWindow(window);
}
}
//----------------------------------------------------------------------------------//
// ムービーウィンドウのアクティベートイベント処理 //
//----------------------------------------------------------------------------------//
void HandleMovieActivate(WindowRef window, Boolean becomeActive)
{
MovieInfoHandle movieInfoHdl;
MovieController controller;
ComponentResult compErr;
GrafPtr savedPort;
GetPort(&savedPort);
SetPort(window);
movieInfoHdl = (MovieInfoHandle)GetWRefCon(window);
if (movieInfoHdl != nil)
{
controller = (*movieInfoHdl)->controller;
// コントローラのアクティベート状態を設定する
compErr = MCActivate(controller, window, becomeActive);
}
SetPort(savedPort);
}
//----------------------------------------------------------------------------------//
// ムービーアクションプロック //
//----------------------------------------------------------------------------------//
pascal Boolean ControllerFilter(MovieController theController,
short action, void *params, long refCon)
{
#pragma unused (params)
Rect bounds;
switch (action)
{
// グローボックスに対する処理を実行する
case mcActionControllerSizeChanged:
// コントローラの境界矩形を取得する
MCGetControllerBoundsRect(theController, &bounds);
// 新しい境界矩形にウィンドウサイズを変更する
SizeWindow((WindowRef) refCon,
bounds.right - bounds.left, bounds.bottom - bounds.top, true);
break;
}
return false;
}
//----------------------------------------------------------------------------------//
// ムービーウィンドウの確認処理 //
//----------------------------------------------------------------------------------//
Boolean IsMovieWindow(WindowRef window)
{
MovieInfoHandle movieInfoHdl = nil;
if (window == nil)
return false;
movieInfoHdl = (MovieInfoHandle)GetWRefCon(window);
if (movieInfoHdl == nil)
return false;
// ウィンドウがムービー情報を記録していることを確認する
if ((*movieInfoHdl)->windowType == MovieFileType)
return true;
else
return false;
}
//----------------------------------------------------------------------------------//
// 既に開いているムービーファイルであるかチェック //
//----------------------------------------------------------------------------------//
static Boolean IsOpenedMovieFIle(const FSSpec *fileSpec)
{
Boolean alreadyOpened = false;
WindowRef window;
MovieInfoHandle movieInfoHdl = nil;
window = FrontWindow();
if (window == nil)
return alreadyOpened;
// 現在表示中の全ウィンドウを順番に評価する
do
{
// ムービーウィンドウであることをチェックする
if (IsMovieWindow(window))
{
movieInfoHdl = (MovieInfoHandle)GetWRefCon(window);
if (movieInfoHdl != nil)
{
// ファイル情報が一致した場合は既に開いていることを意味する
if ((fileSpec->vRefNum == (*movieInfoHdl)->movieFileSpec.vRefNum)
&& (fileSpec->parID == (*movieInfoHdl)->movieFileSpec.parID)
&& (IUEqualString(fileSpec->name,
(*movieInfoHdl)->movieFileSpec.name) == 0))
{
// 該当ウィンドウを前面に移動する
SelectWindow(window);
alreadyOpened = true;
}
}
}
// 次のウィンドウを取得する
window = GetNextWindow(window);
} while ((window != nil) && (alreadyOpened == false));
return alreadyOpened;
}